{
 "cells": [
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 数据类型\n",
    "\n",
    "    Python3有6个标准数据类型： Numbers（数字）、String（字符串）、List（列表）、Tuple（元组）、Sets（集合）、Dictionaries（字典）\n",
    "    \n",
    "**按照是否可变类型**\n",
    "\n",
    "- 不可变：数字、字符串、元组\n",
    "- 可变：列表、集合、字典\n",
    "\n",
    "\n",
    "**元素类型**\n",
    "\n",
    "- 数组：元素可为 数字、字符串、元组、列表、集合、字典\n",
    "- 集合：元素可为 数字、字符串、元组、列表、集合、字典\n",
    "- 集合：元素可为 数字、字符串、元组\n",
    "  - 不可变类型 数字、字符串、元组 都可以；不可变类型 列表、集合、字典 都不行\n",
    "- 字典Key：元素可为 数字、字符串、元组\n",
    "  - 不可变类型 数字、字符串、元组 都可以；不可变类型 列表、集合、字典 都不行\n",
    "- 字典Value：元素可为 数字、字符串、元组、列表、集合、字典"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 65,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "{1: 1, 2: 'cl', 3: [], 4: (), 5: {1}, 6: {}}"
      ]
     },
     "execution_count": 65,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "\"\"\" 数组：元素可为 数字、字符串、元组、列表、集合、字典 \"\"\"\n",
    "[1, \"cl\", [], (), {1}, {}]  # 正常不报错\n",
    "\n",
    "\"\"\" 集合：元素可为 数字、字符串、元组、列表、集合、字典 \"\"\"\n",
    "(1, \"cl\", [], (), {1}, {})  # 正常不报错\n",
    "\n",
    "\"\"\"\n",
    "集合：元素可为 数字、字符串、元组\n",
    "    不可变类型 数字、字符串、元组 都可以；不可变类型 列表、集合、字典 都不行\n",
    "\"\"\"\n",
    "{1, \"str\", ()} # 正常不报错\n",
    "# {[], {1}, {}}  # 报错\n",
    "\n",
    "\n",
    "\"\"\"\n",
    "字典Key：元素可为 数字、字符串、元组\n",
    "  不可变类型 数字、字符串、元组 都可以；不可变类型 列表、集合、字典 都不行\n",
    "\"\"\"\n",
    "{1: 1, \"cl\": 1, (): 2}  # 正常不报错\n",
    "# {[]: 1, {1}: 1, {}: 1}  # 报错\n",
    "\n",
    "\n",
    "# 字典Value：元素可为 数字、字符串、元组、列表、集合、字典\n",
    "{1: 1, 2: \"cl\", 3: [], 4: (), 5: {1}, 6: {}}  # 正常不报错"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 装饰器\n",
    "    装饰器指的定义一个函数，该函数是用来为其他定义函数添加额外功能，就是拓展原来函数功能的一种函数。\n",
    "    \n",
    "**为什么要用wraps**：被装饰后的函数其实已经是另外一个函数了（函数名等函数属性会发生改变），而我们不希望原来函数的属性被覆盖。\n",
    "\n",
    "- 装饰器\n",
    "- 多层装饰器\n",
    "- 带有参数的装饰器\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 29,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "n:3\n",
      "spend: 0.105\n"
     ]
    }
   ],
   "source": [
    "# 装饰器\n",
    "import time\n",
    "from functools import wraps\n",
    "\n",
    "def timmer(func):\n",
    "    @wraps(func) # 修复。加入词句可是被装饰的函数保持原来的函数名和属性\n",
    "    def inner(*args, **kwargs):\n",
    "        start = time.time()\n",
    "        res = func(*args, **kwargs)\n",
    "        stop = time.time()\n",
    "        spend = stop - start\n",
    "        print(f\"spend:{spend: .3f}\")\n",
    "        return res\n",
    "    return inner\n",
    "\n",
    "@timmer\n",
    "def index(n):\n",
    "    time.sleep(0.1)\n",
    "    print(f\"n:{n}\")\n",
    "\n",
    "\n",
    "index(n=3)\n",
    "\n",
    "\"\"\"\n",
    "n:3\n",
    "spend: 0.105\n",
    "\"\"\""
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 33,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "加载了outer3\n",
      "加载了outer2\n",
      "加载了outer1\n",
      "执行了wrapper1\n",
      "执行了wrapper2\n",
      "执行了wrapper3\n",
      "from index\n"
     ]
    }
   ],
   "source": [
    "# 多层装饰器\n",
    "from functools import wraps\n",
    "\n",
    "# 装饰器outer1\n",
    "def outer1(func1):\n",
    "    print('加载了outer1')\n",
    "    @wraps(func1)\n",
    "    def wrapper1(*args, **kwargs):\n",
    "        print('执行了wrapper1')\n",
    "        res1 = func1(*args, **kwargs)\n",
    "        return res1\n",
    "    return wrapper1\n",
    "\n",
    "# 装饰器outer2\n",
    "def outer2(func2):\n",
    "    print('加载了outer2')\n",
    "    @wraps(func2)\n",
    "    def wrapper2(*args, **kwargs):\n",
    "        print('执行了wrapper2')\n",
    "        res2 = func2(*args, **kwargs)\n",
    "        return res2\n",
    "    return wrapper2\n",
    "\n",
    "# 装饰器outer3\n",
    "def outer3(func3):\n",
    "    print('加载了outer3')\n",
    "    @wraps(func3)\n",
    "    def wrapper3(*args, **kwargs):\n",
    "        print('执行了wrapper3')\n",
    "        res3 = func3(*args, **kwargs)\n",
    "        return res3\n",
    "    return wrapper3\n",
    "    \n",
    "# 连用三个语法糖\n",
    "@outer1\n",
    "@outer2\n",
    "@outer3\n",
    "def index():\n",
    "    print('from index')\n",
    "    \n",
    "# index = outer3(outer2(outer1(index))) 就相当于执行力这段语句。\n",
    "\n",
    "index()\n",
    "\"\"\" 输出:\n",
    "\n",
    "加载了outer3\n",
    "加载了outer2\n",
    "加载了outer1\n",
    "执行了wrapper1\n",
    "执行了wrapper2\n",
    "执行了wrapper3\n",
    "from index\n",
    "\n",
    "\"\"\""
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 44,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "操作方式3\n",
      "from index\n"
     ]
    }
   ],
   "source": [
    "from functools import wraps\n",
    "\n",
    "# 有参数的装饰器\n",
    "def outer_outer(source_data):\n",
    "    def outer(func):\n",
    "        @wraps(func)\n",
    "        def inner(*args, **kwargs): \n",
    "            if source_data == 1:\n",
    "                print('操作方式1')\n",
    "            elif source_data == 2:\n",
    "                print('操作方式2')\n",
    "            elif source_data == 3:\n",
    "                print('操作方式3')\n",
    "            else:\n",
    "                print('其他操作情况')\n",
    "            res = func(*args, **kwargs)\n",
    "        return inner\n",
    "    return outer\n",
    "\n",
    "@outer_outer(source_data=3)\n",
    "def index():\n",
    "    print(\"from index\")\n",
    "    \n",
    "index()\n",
    "\"\"\" 输出:\n",
    "操作方式3\n",
    "from index\n",
    "\"\"\""
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 单例模式"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 55,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "(4373523192, 4373523192)"
      ]
     },
     "execution_count": 55,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "# 重写 __new__ 方法\n",
    "\n",
    "def Single():\n",
    "    instance = None\n",
    "    def __new__(cls, *args, **kwargs):\n",
    "        if cls.instance is None:\n",
    "            cls.instance = super().__new__(cls, *args, **kwargs)\n",
    "        return cls.instance\n",
    "    \n",
    "\n",
    "s1 = Single() \n",
    "s2 = Single() \n",
    "\n",
    "id(s1), id(s2)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "这是A的类的初始化方法\n"
     ]
    },
    {
     "data": {
      "text/plain": [
       "(140445708763680, 140445708763680)"
      ]
     },
     "execution_count": 5,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "def singleton(cls):\n",
    "    # 创建一个字典用来保存类的实例对象\n",
    "    _instance = {}\n",
    "    def _singleton(*args, **kwargs):\n",
    "        # 先判断这个类有没有对象\n",
    "        if cls not in _instance:\n",
    "            _instance[cls] = cls(*args, **kwargs)  # 创建一个对象,并保存到字典当中\n",
    "        # 将实例对象返回\n",
    "        return _instance[cls]\n",
    "    return _singleton\n",
    "\n",
    "\n",
    "@singleton\n",
    "class TestClass(object):\n",
    "    a = 1\n",
    "\n",
    "    def __init__(self, x=0):\n",
    "        self.x = x\n",
    "        self.a = x\n",
    "        print('这是A的类的初始化方法')\n",
    "\n",
    "    def show(self):\n",
    "        print(self.x)\n",
    "        print(self.a)\n",
    "\n",
    "        \n",
    "t1 = TestClass()\n",
    "t2 = TestClass()\n",
    "\n",
    "id(t1), id(t2)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 9,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "<__main__.TestClass at 0x7fbc1094c220>"
      ]
     },
     "execution_count": 9,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "t1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "import tensorflow as tf"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.8.5"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 4
}
